<template>
  <div>
    <!-- 主界面 -->
    <button @click="startScreenshot">开始截图</button>
    
    <!-- 截图遮罩层 -->
    <div v-if="isScreenshotMode" class="screenshot-overlay" ref="overlay"
         @mousedown="startSelection">
      <!-- 非选中区域的遮罩 -->
      <div class="mask" :style="getMaskStyle()"></div>
      
      <!-- 截图区域 - 只在有选择时显示 -->
      <div 
        v-if="hasSelection"
        class="selection-area" 
        :style="{
          left: `${normalizedSelection.left}px`,
          top: `${normalizedSelection.top}px`,
          width: `${normalizedSelection.width}px`,
          height: `${normalizedSelection.height}px`,
          cursor: isDragging ? 'grabbing' : 'grab'
        }"
        @mousedown="startDrag"
      >
        <!-- 八个方向的调整点 -->
        <div class="resize-handle top-left" @mousedown.stop="startResize($event, 'top-left')"></div>
        <div class="resize-handle top-right" @mousedown.stop="startResize($event, 'top-right')"></div>
        <div class="resize-handle bottom-left" @mousedown.stop="startResize($event, 'bottom-left')"></div>
        <div class="resize-handle bottom-right" @mousedown.stop="startResize($event, 'bottom-right')"></div>
        <div class="resize-handle top-center" @mousedown.stop="startResize($event, 'top')"></div>
        <div class="resize-handle bottom-center" @mousedown.stop="startResize($event, 'bottom')"></div>
        <div class="resize-handle left-center" @mousedown.stop="startResize($event, 'left')"></div>
        <div class="resize-handle right-center" @mousedown.stop="startResize($event, 'right')"></div>
        
        <!-- 工具栏 -->
        <div class="toolbar">
          <button @click="confirmScreenshot" title="确认截图">✓</button>
          <button @click="cancelScreenshot" title="取消截图">✕</button>
        </div>
      </div>
      
      <!-- 尺寸提示 -->
      <div 
        class="size-hint" 
        v-if="hasSelection"
        :style="{
          left: `${normalizedSelection.left + normalizedSelection.width + 10}px`,
          top: `${normalizedSelection.top + normalizedSelection.height + 10}px`
        }"
      >
        {{ normalizedSelection.width }} × {{ normalizedSelection.height }}
      </div>
    </div>
    
    <!-- 预览区域 -->
    <div v-if="screenshotResult" class="preview-container">
      <img :src="screenshotResult" alt="截图结果" class="preview-image" />
      <div class="preview-actions">
        <button @click="downloadScreenshot">下载</button>
        <button @click="copyToClipboard">复制</button>
        <button @click="closePreview">关闭</button>
      </div>
    </div>
  </div>
</template>

<script setup>
import { ref, computed, onMounted, onUnmounted } from 'vue';
import html2canvas from 'html2canvas';

const isScreenshotMode = ref(false);
const screenshotResult = ref(null);
const overlay = ref(null);
const isDragging = ref(false);
const isSelecting = ref(false); // 是否正在选择中

const selection = ref({
  startX: 0,
  startY: 0,
  endX: 0,
  endY: 0
});

// 计算规范化后的选区（确保宽度和高度为正数）
const normalizedSelection = computed(() => {
  const left = Math.min(selection.value.startX, selection.value.endX);
  const top = Math.min(selection.value.startY, selection.value.endY);
  const width = Math.abs(selection.value.endX - selection.value.startX);
  const height = Math.abs(selection.value.endY - selection.value.startY);
  
  return { left, top, width, height };
});

const hasSelection = computed(() => {
  return isSelecting.value && normalizedSelection.value.width > 10 && normalizedSelection.value.height > 10;
});

// 获取遮罩层样式（排除选中区域）
const getMaskStyle = () => {
  if (!hasSelection.value) return { backgroundColor: 'rgba(0, 0, 0, 0.4)' };
  
  const { left, top, width, height } = normalizedSelection.value;
  
  return {
    clipPath: `polygon(
      0% 0%, 
      0% 100%, 
      ${left}px 100%, 
      ${left}px ${top}px, 
      ${left + width}px ${top}px, 
      ${left + width}px ${top + height}px, 
      ${left}px ${top + height}px, 
      ${left}px 100%, 
      100% 100%, 
      100% 0%
    )`,
    backgroundColor: 'rgba(0, 0, 0, 0.4)'
  };
};

// 开始截图模式
const startScreenshot = () => {
  isScreenshotMode.value = true;
  isSelecting.value = false; // 初始状态为未开始选择
  resetSelection();
  document.body.style.overflow = 'hidden';
};

// 开始选择区域
const startSelection = (e) => {
  if (!isScreenshotMode.value || isSelecting.value) return;
  if (e.button !== 0) return; // 只响应左键
  
  isSelecting.value = true;
  
  dragState.value = {
    isDragging: false,
    isResizing: false,
    isCreating: true,
    startX: e.clientX,
    startY: e.clientY,
    originalSelection: { ...selection.value }
  };
  
  selection.value = {
    startX: e.clientX,
    startY: e.clientY,
    endX: e.clientX,
    endY: e.clientY
  };
  
  e.preventDefault();
  e.stopPropagation();
};

// 重置选择区域
const resetSelection = () => {
  selection.value = {
    startX: 0,
    startY: 0,
    endX: 0,
    endY: 0
  };
};

// 开始拖动选择区域
const startDrag = (e) => {
  if (e.button !== 0) return; // 只响应左键
  
  if (hasSelection.value) {
    // 拖动整个选区
    isDragging.value = true;
    dragState.value = {
      isDragging: true,
      isResizing: false,
      isCreating: false,
      startX: e.clientX,
      startY: e.clientY,
      originalSelection: { ...selection.value }
    };
  }
  
  e.preventDefault();
  e.stopPropagation();
};

const dragState = ref({
  isDragging: false,
  isResizing: false,
  isCreating: false,
  resizeDirection: '',
  startX: 0,
  startY: 0,
  originalSelection: {}
});

// 开始调整大小
const startResize = (e, direction) => {
  if (e.button !== 0) return; // 只响应左键
  
  dragState.value = {
    isDragging: false,
    isResizing: true,
    isCreating: false,
    resizeDirection: direction,
    startX: e.clientX,
    startY: e.clientY,
    originalSelection: { ...selection.value }
  };
  
  e.preventDefault();
  e.stopPropagation();
};

// 鼠标移动处理
const handleMouseMove = (e) => {
  if (!isScreenshotMode.value) return;
  
  // 创建新选区
  if (dragState.value.isCreating) {
    selection.value = {
      ...selection.value,
      endX: e.clientX,
      endY: e.clientY
    };
    return;
  }
  
  // 拖动选区
  if (dragState.value.isDragging) {
    const dx = e.clientX - dragState.value.startX;
    const dy = e.clientY - dragState.value.startY;
    
    selection.value = {
      startX: dragState.value.originalSelection.startX + dx,
      startY: dragState.value.originalSelection.startY + dy,
      endX: dragState.value.originalSelection.endX + dx,
      endY: dragState.value.originalSelection.endY + dy
    };
    return;
  }
  
  // 调整选区大小
  if (dragState.value.isResizing) {
    const dx = e.clientX - dragState.value.startX;
    const dy = e.clientY - dragState.value.startY;
    
    const { originalSelection, resizeDirection } = dragState.value;
    
    let newSelection = { ...originalSelection };
    
    switch (resizeDirection) {
      case 'top-left':
        newSelection.startX = originalSelection.startX + dx;
        newSelection.startY = originalSelection.startY + dy;
        break;
      case 'top-right':
        newSelection.endX = originalSelection.endX + dx;
        newSelection.startY = originalSelection.startY + dy;
        break;
      case 'bottom-left':
        newSelection.startX = originalSelection.startX + dx;
        newSelection.endY = originalSelection.endY + dy;
        break;
      case 'bottom-right':
        newSelection.endX = originalSelection.endX + dx;
        newSelection.endY = originalSelection.endY + dy;
        break;
      case 'top':
        newSelection.startY = originalSelection.startY + dy;
        break;
      case 'bottom':
        newSelection.endY = originalSelection.endY + dy;
        break;
      case 'left':
        newSelection.startX = originalSelection.startX + dx;
        break;
      case 'right':
        newSelection.endX = originalSelection.endX + dx;
        break;
    }
    
    // 确保最小尺寸
    const minSize = 10;
    if (Math.abs(newSelection.endX - newSelection.startX) < minSize) {
      if (resizeDirection.includes('left')) {
        newSelection.startX = newSelection.endX - (minSize * Math.sign(newSelection.endX - newSelection.startX));
      } else if (resizeDirection.includes('right')) {
        newSelection.endX = newSelection.startX + (minSize * Math.sign(newSelection.endX - newSelection.startX));
      }
    }
    
    if (Math.abs(newSelection.endY - newSelection.startY) < minSize) {
      if (resizeDirection.includes('top')) {
        newSelection.startY = newSelection.endY - (minSize * Math.sign(newSelection.endY - newSelection.startY));
      } else if (resizeDirection.includes('bottom')) {
        newSelection.endY = newSelection.startY + (minSize * Math.sign(newSelection.endY - newSelection.startY));
      }
    }
    
    selection.value = newSelection;
    return;
  }
  
  // 初始状态，跟随鼠标显示十字光标
  if (!isSelecting.value) {
    overlay.value.style.cursor = 'crosshair';
  }
};

// 鼠标释放处理
const handleMouseUp = () => {
  isDragging.value = false;
  dragState.value = {
    isDragging: false,
    isResizing: false,
    isCreating: false,
    resizeDirection: '',
    startX: 0,
    startY: 0,
    originalSelection: {}
  };
};

// 确认截图
const confirmScreenshot = async () => {
  try {
    const { left, top, width, height } = normalizedSelection.value;
    
    const canvas = await html2canvas(document.body, {
      x: left,
      y: top,
      width: width,
      height: height,
      scale: 1,
      logging: false,
      useCORS: true,
      backgroundColor: null
    });
    
    screenshotResult.value = canvas.toDataURL('image/png');
    isScreenshotMode.value = false;
    isSelecting.value = false;
    document.body.style.overflow = '';
  } catch (error) {
    console.error('截图失败:', error);
    cancelScreenshot();
  }
};

// 取消截图
const cancelScreenshot = () => {
  isScreenshotMode.value = false;
  isSelecting.value = false;
  screenshotResult.value = null;
  document.body.style.overflow = '';
};

// 下载截图
const downloadScreenshot = () => {
  if (!screenshotResult.value) return;
  
  const link = document.createElement('a');
  link.download = `screenshot-${new Date().getTime()}.png`;
  link.href = screenshotResult.value;
  link.click();
};

// 复制到剪贴板
const copyToClipboard = async () => {
  try {
    const blob = await (await fetch(screenshotResult.value)).blob();
    
    await navigator.clipboard.write([
      new ClipboardItem({
        [blob.type]: blob
      })
    ]);
    alert('截图已复制到剪贴板');
  } catch (error) {
    console.error('复制失败:', error);
    alert('复制失败，请尝试下载截图');
  }
};

// 关闭预览
const closePreview = () => {
  screenshotResult.value = null;
};

// 添加事件监听
onMounted(() => {
  document.addEventListener('mousemove', handleMouseMove);
  document.addEventListener('mouseup', handleMouseUp);
});

// 移除事件监听
onUnmounted(() => {
  document.removeEventListener('mousemove', handleMouseMove);
  document.removeEventListener('mouseup', handleMouseUp);
});
</script>

<style scoped>
.screenshot-overlay {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  z-index: 9999;
  cursor: crosshair;
}

.mask {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
}

.selection-area {
  position: absolute;
  border: 2px solid #07C160;
  z-index: 1;
  background-color: transparent;
}

.resize-handle {
  position: absolute;
  width: 8px;
  height: 8px;
  background-color: #07C160;
  border: 1px solid white;
  z-index: 2;
}

.top-left {
  top: -4px;
  left: -4px;
  cursor: nwse-resize;
}

.top-right {
  top: -4px;
  right: -4px;
  cursor: nesw-resize;
}

.bottom-left {
  bottom: -4px;
  left: -4px;
  cursor: nesw-resize;
}

.bottom-right {
  bottom: -4px;
  right: -4px;
  cursor: nwse-resize;
}

.top-center {
  top: -4px;
  left: 50%;
  margin-left: -4px;
  cursor: ns-resize;
}

.bottom-center {
  bottom: -4px;
  left: 50%;
  margin-left: -4px;
  cursor: ns-resize;
}

.left-center {
  top: 50%;
  left: -4px;
  margin-top: -4px;
  cursor: ew-resize;
}

.right-center {
  top: 50%;
  right: -4px;
  margin-top: -4px;
  cursor: ew-resize;
}

.toolbar {
  position: absolute;
  bottom: -40px;
  right: 0;
  display: flex;
  background-color: #07C160;
  border-radius: 4px;
  padding: 4px;
  gap: 4px;
}

.toolbar button {
  width: 28px;
  height: 28px;
  background: none;
  border: none;
  color: white;
  cursor: pointer;
  border-radius: 2px;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 16px;
}

.toolbar button:hover {
  background-color: rgba(255, 255, 255, 0.2);
}

.size-hint {
  position: absolute;
  background-color: rgba(0, 0, 0, 0.7);
  color: white;
  padding: 4px 8px;
  border-radius: 4px;
  font-size: 12px;
  z-index: 2;
}

.preview-container {
  position: fixed;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  background-color: white;
  padding: 20px;
  border-radius: 8px;
  box-shadow: 0 0 20px rgba(0, 0, 0, 0.2);
  z-index: 10000;
}

.preview-image {
  max-width: 80vw;
  max-height: 80vh;
  display: block;
  margin-bottom: 16px;
}

.preview-actions {
  display: flex;
  justify-content: center;
  gap: 12px;
}

.preview-actions button {
  padding: 8px 16px;
  background-color: #07C160;
  color: white;
  border: none;
  border-radius: 4px;
  cursor: pointer;
}

.preview-actions button:hover {
  background-color: #06AD56;
}

button {
  padding: 8px 16px;
  background-color: #07C160;
  color: white;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  margin: 10px;
}

button:hover {
  background-color: #06AD56;
}
</style>